package com.ego.ware.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.ego.common.constant.SystemConstant;
import com.ego.common.constant.WareConstant;
import com.ego.common.exception.GlobalException;
import com.ego.common.util.PageUtil;
import com.ego.common.util.Result;
import com.ego.common.vo.PageVo;
import com.ego.ware.feign.ProductFeign;
import com.ego.ware.po.Purchase;
import com.ego.ware.po.WareInfo;
import com.ego.ware.service.PurchaseService;
import com.ego.ware.service.WareInfoService;
import com.ego.ware.vo.PurchaseDetailSearchVo;
import com.ego.ware.vo.PurchaseDetailVo;
import com.ego.ware.vo.PurchaseMergeVo;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;

import com.ego.ware.dao.PurchaseDetailDao;
import com.ego.ware.po.PurchaseDetail;
import com.ego.ware.service.PurchaseDetailService;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * @program: ego
 * @description 对应实现类
 * @author KamTang
 * @date 2022-11-13 13:30:29
 */
@Service("purchaseDetailService")
public class PurchaseDetailServiceImpl extends ServiceImpl<PurchaseDetailDao, PurchaseDetail> implements PurchaseDetailService {

    @Autowired
    private ProductFeign productFeign;
    @Autowired
    private WareInfoService wareInfoService;
    @Autowired
    @Lazy
    private PurchaseService purchaseService;

    @Override
    public PageVo<PurchaseDetailVo> search(PurchaseDetailSearchVo search) {
        LambdaQueryWrapper<PurchaseDetail> query = Wrappers.<PurchaseDetail>lambdaQuery()
                .eq(search.getStatus() != null, PurchaseDetail::getStatus, search.getStatus())
                .eq(search.getWareId() != null, PurchaseDetail::getWareId, search.getWareId());
        if (StringUtils.isNotEmpty(search.getKeyword())) {
            query.eq(PurchaseDetail::getPurchaseId, search.getKeyword())
                    .eq(PurchaseDetail::getSkuId, search.getKeyword());

        }
        Page<PurchaseDetail> page = this.baseMapper.selectPage(Page.of(search.getPageNum(), search.getPageSize()), query);
        List<PurchaseDetailVo> vos = page.getRecords().stream().map(PurchaseDetail::toVo).collect(Collectors.toList());
        return PageUtil.toPage(page, vos);
    }

    @Override
    public void save(PurchaseDetailVo purchaseDetailVo) {
        Result skuResp = productFeign.get(purchaseDetailVo.getSkuId());
        if (skuResp.getCode() == SystemConstant.Status.SUCCESS.getCode()) {
            Map<String, Object> skuInfo = JSONObject.parseObject(JSON.toJSONString(skuResp.get("skuInfo")));
            String skuName = (String) skuInfo.get("skuName");
            BigDecimal price = (BigDecimal) skuInfo.get("price");
            purchaseDetailVo.setSkuName(skuName);
            purchaseDetailVo.setSkuPrice(price);
        }
        WareInfo wareInfo = wareInfoService.getById(purchaseDetailVo.getWareId());
        purchaseDetailVo.setWareName(wareInfo.getName());
        this.save(PurchaseDetail.fromVo(purchaseDetailVo));
    }

    @Override
    public PurchaseDetailVo get(Long id) {
        PurchaseDetail purchaseDetail = this.getById(id);
        PurchaseDetailVo purchaseDetailVo = purchaseDetail.toVo();
        Result catPathResp = productFeign.getCatPath(purchaseDetail.getCategoryId());
        if (catPathResp.getCode() == SystemConstant.Status.SUCCESS.getCode()) {
            Map<String, Object> map = JSONObject.parseObject(JSON.toJSONString(catPathResp.get("categoryPath")));
            Object obj = map.get("list");
            List<Long> categoryPaths = JSONObject.parseArray(obj.toString(), Long.class);
            purchaseDetailVo.setCategoryPath(categoryPaths);
        }
        return purchaseDetailVo;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean merge(PurchaseMergeVo mergeVo) {
        Long purchaseId = mergeVo.getPurchaseId();
        if (purchaseId == null) {
            Purchase purchase = new Purchase();
            purchase.setStatus(WareConstant.PurchaseStatusEnum.CREATED.getCode());
            purchase.setCreateTime(new Date());
            purchase.setUpdateTime(new Date());
            purchaseService.save(purchase);
        }

        List<Long> items = mergeVo.getItems();
        List<PurchaseDetail> purchaseDetails = this.listByIds(items).stream().peek(purchaseDetail -> {
            if (!purchaseDetail.mergeable()) {
                throw new GlobalException("采购单状态为“新建”或者“已分配”才能进行合并", 500);
            }
            purchaseDetail.assign(mergeVo.getPurchaseId());
        }).collect(Collectors.toList());
        this.updateBatchById(purchaseDetails);

        Purchase purchase = new Purchase();
        BigDecimal total = BigDecimal.ZERO;
        for (PurchaseDetail purchaseDetail : purchaseDetails) {
            total = total.add(purchaseDetail.getSkuPrice().multiply(new BigDecimal(purchaseDetail.getSkuNum())));
        }
        purchase.setId(mergeVo.getPurchaseId());
        purchase.setUpdateTime(new Date());
        purchase.setAmount(total);
        return purchaseService.updateById(purchase);
    }
}
